{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Multivariable control\n", "You may want to review the [Transfer function matrix](../../1_Dynamics/6_Multivariable_system_representation/Transfer%20function%20matrices.ipynb) notebook before you look at this one.\n", "\n", "## Closed loop transfer functions for multivariable systems\n", "\n", "Let's consider a 2 $\\times$ 2 system with feedback control as shown below:\n", "\n", "![2x2mimo](../../assets/mimo2x2.png)\n" ] }, { "cell_type": "code", "execution_count": 1, "metadata": { "collapsed": true }, "outputs": [], "source": [ "import sympy\n", "sympy.init_printing()" ] }, { "cell_type": "code", "execution_count": 2, "metadata": {}, "outputs": [], "source": [ "G_p11, G_p12, G_p21, G_p22, G_c1, G_c2 = sympy.symbols('G_p11, G_p12, G_p21, G_p22, G_c1, G_c2')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The matrix representation of the system is straigtforwardly handled by `sympy.Matrix`:" ] }, { "cell_type": "code", "execution_count": 3, "metadata": { "collapsed": true }, "outputs": [], "source": [ "G_p = sympy.Matrix([[G_p11, G_p12],\n", " [G_p21, G_p22]])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The controller is a bit harder. Convince yourself you understand how the off-diagonal elements of $G_c$ are zero in the diagram above." ] }, { "cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [], "source": [ "G_c = sympy.Matrix([[G_c1, 0],\n", " [0, G_c2]])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now, we can redraw the block diagram using vectors for the signals and matrices for the blocks.\n", " \n", "![Simple feedback](../../assets/simple_feedback.png)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's derive the closed loop transfer function. There are three equations represented in the above diagram:\n", "\n", "\\begin{align}\n", "E &= Y_{sp} - Y\\\\ \n", "U &= G_c E = G_c(Y_{sp} - Y)\\\\\n", "Y &= G_p U = G_p G_c(Y_{sp} - Y)\\\\\n", "\\end{align}\n", "\n", "Now, we can solve for $Y$:\n", "\n", "\\begin{align}\n", "Y &= G_p G_c(Y_{sp} - Y)\\\\\n", "Y &= G_p G_c Y_{sp} - G_p G_c Y \\\\\n", "Y + G_p G_c Y&= G_p G_c Y_{sp} \\\\\n", "(I + G_p G_c) Y &= G_p G_c Y_{sp} \\\\\n", " Y &= (I + G_p G_c)^{-1} G_p G_c Y_{sp} \\\\\n", " Y &= \\Gamma Y_{sp}\n", "\\end{align}" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We can calculate the value of this function easily." ] }, { "cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [], "source": [ "I = sympy.Matrix([[1, 0],\n", " [0, 1]])" ] }, { "cell_type": "code", "execution_count": 6, "metadata": {}, "outputs": [], "source": [ "Gamma = sympy.simplify((I + G_p*G_c).inv()*G_p*G_c)" ] }, { "cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [ { "data": { "image/png": "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\ny7P3nJbh/Rc6e3V7A4BsCgAAAABJRU5ErkJggg==\n", "text/latex": [ "$$\\frac{G_{c1} \\left(G_{c2} G_{p12} G_{p21} - G_{p11} \\left(G_{c2} G_{p22} + 1\\right)\\right)}{G_{c1} G_{c2} G_{p12} G_{p21} - \\left(G_{c1} G_{p11} + 1\\right) \\left(G_{c2} G_{p22} + 1\\right)}$$" ], "text/plain": [ " G_c1⋅(G_c2⋅Gₚ₁₂⋅Gₚ₂₁ - Gₚ₁₁⋅(G_c2⋅Gₚ₂₂ + 1)) \n", "─────────────────────────────────────────────────────\n", "G_c1⋅G_c2⋅Gₚ₁₂⋅Gₚ₂₁ - (G_c1⋅Gₚ₁₁ + 1)⋅(G_c2⋅Gₚ₂₂ + 1)" ] }, "execution_count": 7, "metadata": {}, "output_type": "execute_result" } ], "source": [ "Gamma[0, 0]" ] }, { "cell_type": "code", "execution_count": 8, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n+h0SvfFR/gAAAABJRU5ErkJggg==\n", "text/latex": [ "$$- \\frac{G_{c2} G_{p12}}{G_{c1} G_{c2} G_{p12} G_{p21} - \\left(G_{c1} G_{p11} + 1\\right) \\left(G_{c2} G_{p22} + 1\\right)}$$" ], "text/plain": [ " -G_c2⋅Gₚ₁₂ \n", "─────────────────────────────────────────────────────\n", "G_c1⋅G_c2⋅Gₚ₁₂⋅Gₚ₂₁ - (G_c1⋅Gₚ₁₁ + 1)⋅(G_c2⋅Gₚ₂₂ + 1)" ] }, "execution_count": 8, "metadata": {}, "output_type": "execute_result" } ], "source": [ "Gamma[0, 1]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We notice that there is a common divisor in all the elements of $\\Gamma$. This is due to the calculation of the inverse of $(I + G_p G_c)$, which involves calculation of the determinant $|I + G_p G_c|$." ] }, { "cell_type": "code", "execution_count": 9, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/latex": [ "$$G_{c1} G_{c2} G_{p11} G_{p22} - G_{c1} G_{c2} G_{p12} G_{p21} + G_{c1} G_{p11} + G_{c2} G_{p22} + 1$$" ], "text/plain": [ "G_c1⋅G_c2⋅Gₚ₁₁⋅Gₚ₂₂ - G_c1⋅G_c2⋅Gₚ₁₂⋅Gₚ₂₁ + G_c1⋅Gₚ₁₁ + G_c2⋅Gₚ₂₂ + 1" ] }, "execution_count": 9, "metadata": {}, "output_type": "execute_result" } ], "source": [ "Delta = (I + G_p*G_c).det()\n", "Delta" ] }, { "cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [ { "data": { "image/png": "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\nYII=\n", "text/latex": [ "$$\\left[\\begin{matrix}G_{c1} \\left(G_{c2} G_{p11} G_{p22} - G_{c2} G_{p12} G_{p21} + G_{p11}\\right) & G_{c2} G_{p12}\\\\G_{c1} G_{p21} & G_{c2} \\left(G_{c1} G_{p11} G_{p22} - G_{c1} G_{p12} G_{p21} + G_{p22}\\right)\\end{matrix}\\right]$$" ], "text/plain": [ "⎡G_c1⋅(G_c2⋅Gₚ₁₁⋅Gₚ₂₂ - G_c2⋅Gₚ₁₂⋅Gₚ₂₁ + Gₚ₁₁) G_c2⋅Gₚ₁₂ \n", "⎢ \n", "⎣ G_c1⋅Gₚ₂₁ G_c2⋅(G_c1⋅Gₚ₁₁⋅Gₚ₂₂ - G_c1⋅Gₚ\n", "\n", " ⎤\n", " ⎥\n", "₁₂⋅Gₚ₂₁ + Gₚ₂₂)⎦" ] }, "execution_count": 10, "metadata": {}, "output_type": "execute_result" } ], "source": [ "(Delta*Gamma).simplify()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Characteristic equation\n", "-----------------------\n", "\n", "This leads us to conclude that we can calculate the characteristic equation of the closed loop transfer function as $|I + G_p G_c|$." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Notice that if we wanted the coupling the other way around, we could have worked with the same controller matrix permuted:" ] }, { "cell_type": "code", "execution_count": 11, "metadata": {}, "outputs": [ { "data": { "image/png": "iVBORw0KGgoAAAANSUhEUgAAAGMAAAAyBAMAAAC6x3j0AAAAMFBMVEX///8AAAAAAAAAAAAAAAAA\nAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAv3aB7AAAAD3RSTlMA74lUMhCZZs3dIrur\nRHbLQ9+lAAAACXBIWXMAAA7EAAAOxAGVKw4bAAACSElEQVRIDe2Wz0sbQRTHv24yMYmsBip4dA9C\npYeSUigUDwlUxVuih4KXuhRKBUFtDz22Qi8eBW+CNvTgVa+iBw8iCqXkPzB/gEjRWmip3c5k582P\nnW1JWuipA9n35r33mZ+bL4vh6BKdNy+KSrg1PtE5ATb+qITBLgBRmjWRx7dH0vAnBx+W3+uEhbzF\nbEOnyOsfAh7wHzUT6S3BW6GEsmyvDuS+qb61sL5DZK51Snp5EfLXdNycZeAQ/pVOSW9pmTvZUMdN\nZC6E/0OnYq/4VVjW4A/ZTGQnQNa5Vc8cZEpQFhKmIIXPNDoweZpEUhfW8wnon18N2uDDJMK3n3G2\nX+AIvJs2AQfp20Wvc8jtG8lzzrtouQi/ytxKPJx+FsWB1Hh4k2/bmQXrmK7qYulVWsieBsjtsmoK\nMnNx5BBgC8fPM030lHnKncWt15GBRtdIvokQ98QQ5lWK/i9bcfF1ffvdR57vGNFj/Uf+Ssf0Qf7O\nU4ec0LcEw56+rFKIkKS+UV7afJltUEgijr5RXtoXwCiFJOLoG+WlPQAqdelLxNG3BPIdOBN/GNFi\nxNW3OEtP9oUjLdmLEVPfvIVnVKmsEIBaYCGmvt3BiSolp8hnSSCmvm2g1qBSsikLM/VtEztNKlWW\nb79ib9/SN32cisA+8MY+ZEvfsKVLyeNXOU++vBdT37yQktoWyky98BIx9e2VrlQeu3tepY5EZFfo\nmx/4KktVlrURoW9T98doo1al6tiI0LfhKFLZVMdGUkuSwX+G/MHHVfefcD8B0NGI3QzY8lkAAAAA\nSUVORK5CYII=\n", "text/latex": [ "$$\\left[\\begin{matrix}0 & G_{c1}\\\\G_{c2} & 0\\end{matrix}\\right]$$" ], "text/plain": [ "⎡ 0 G_c1⎤\n", "⎢ ⎥\n", "⎣G_c2 0 ⎦" ] }, "execution_count": 11, "metadata": {}, "output_type": "execute_result" } ], "source": [ "G_c*sympy.Matrix([[0, 1], [1, 0]])" ] } ], "metadata": { "anaconda-cloud": {}, "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.8.8" } }, "nbformat": 4, "nbformat_minor": 2 }